package org.jiuling.tencentcloud.cos.client.builder;

import com.qcloud.cos.COSClient;
import com.qcloud.cos.auth.BasicSessionCredentials;
import com.qcloud.cos.auth.COSCredentials;
import com.qcloud.cos.region.Region;
import com.tencent.cloud.CosStsClient;
import com.tencent.cloud.Response;
import org.jiuling.tencentcloud.cos.client.factory.CosClientFactory;
import org.jiuling.tencentcloud.cos.client.util.COSClientUtil;
import org.jiuling.tencentcloud.cos.config.TencentCosConfig;
import org.jiuling.tencentcloud.cos.config.TencentCosStsConfig;

import java.io.IOException;
import java.util.TreeMap;

/**
 * CosSts客户端生成器
 * @author 紫灵
 * @date 2024年02月23日 19时11分57秒
 */
public class CosStsClientBuilder implements CosClientFactory {

    /** 腾讯云对象存储配置 */
    private final TencentCosConfig tencentCosConfig;
    /** 腾讯CosSts配置 */
    private final TencentCosStsConfig tencentCosStsConfig;

    public CosStsClientBuilder(TencentCosConfig tencentCosConfig, TencentCosStsConfig tencentCosStsConfig) {
        this.tencentCosConfig = tencentCosConfig;
        this.tencentCosStsConfig = tencentCosStsConfig;
    }

    @Override
    public COSClient builderCosClient() {

        TreeMap<String, Object> config = new TreeMap<String, Object>();

        // 密钥 SecretId
        config.put("secretId", tencentCosConfig.getSecretId());
        // 密钥 SecretKey
        config.put("secretKey", tencentCosConfig.getSecretKey());

        // 临时密钥有效时长，单位是秒，默认 1800 秒，目前主账号最长 2 小时（即 7200 秒），子账号最长 36 小时（即 129600）秒
        config.put("durationSeconds", tencentCosStsConfig.getDurationSeconds());

        // 换成您的 bucket
        config.put("bucket", tencentCosConfig.getBucketName());
        // 换成 bucket 所在地区
        config.put("region", tencentCosConfig.getBucketAddr());

        // 这里改成允许的路径前缀，可以根据自己网站的用户登录态判断允许上传的具体路径
        // 列举几种典型的前缀授权场景：
        // 1、允许访问所有对象："*"
        // 2、允许访问指定的对象："a/a1.txt", "b/b1.txt"
        // 3、允许访问指定前缀的对象："a*", "a/*", "b/*"
        // 如果填写了“*”，将允许用户访问所有资源；除非业务需要，否则请按照最小权限原则授予用户相应的访问权限范围。
        config.put("allowPrefixes", tencentCosStsConfig.getAllowPrefixes());

        // 密钥的权限列表。必须在这里指定本次临时密钥所需要的权限。
        // 简单上传、表单上传和分块上传需要以下的权限，其他权限列表请参见 https://cloud.tencent.com/document/product/436/31923
        config.put("allowActions", tencentCosStsConfig.getAllowActions());

        try {
            Response response = CosStsClient.getCredential(config);
            // 初始化用户身份信息（secretId, secretKey）。
            COSCredentials cred = new BasicSessionCredentials(
                    response.credentials.tmpSecretId,
                    response.credentials.tmpSecretKey,
                    response.credentials.sessionToken
            );
            // 设置存储桶的地域（上文获得）
            Region region = new Region(tencentCosConfig.getBucketAddr());
            return COSClientUtil.getCosClient(cred,region);
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }
}
